using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using Rally_Dekstop.RallyAPI_UseCase;
using System.Collections;
using System.Resources;
using System.Threading;

namespace Rally_Dekstop
{
    public partial class LoginForm : Form
    {
        private const string hashkey = "Password";
        private const string LOGININFO = "LoginInfo";
        private const string LOGINNAME = "Login";
        private const string PASSWORD = "Password";
        private const string REMEMBERME = "RememberMeStatus";
        private const string RECENT_INFO = "RecentInfo";
        private const string HOSTNAME = "HostName";
        ArrayList wk = null;

        private object parent = null;

        object[] args = new object[3];

        private ResourceManager m_ResourceManager = Localizer.getInstance().GetResourceManager();

        private IRallyService service = null;

        public LoginForm(object listener)
        {
            InitializeComponent();
            parent = listener;

            
            hostname_comboBox.Items.Add("rally1");
            hostname_comboBox.Items.Add("trial");
            hostname_comboBox.Items.Add("community");
                                  
        }
        
        private void button1_Click(object sender, EventArgs e)
        {
            
            try
            {
                if (hostname_comboBox.Text == string.Empty)
                {
                    MessageBox.Show("Hostname cannot be blank. Please select Hostname...", m_ResourceManager.GetString("memo://rallydesk/RallyDeskCaption"), MessageBoxButtons.OK, MessageBoxIcon.Warning);
                    return;
                }

                this.Cursor = Cursors.WaitCursor;
                this.Enabled = false;
                RallyDesk.Username = cmbUserName.Text;
                RallyDesk.Password = txtPassword.Text;
                RallyDesk.HOSTNAME = hostname_comboBox.Text;

                //if (chkRememberMe.Checked)
                //    SaveEnteriesInRegistry();
                if (service == null)
                    service = new RallyAPIUseCase(string.Empty);
                
                args[0] = cmbUserName.Text;
                args[1] = txtPassword.Text;
                args[2] = hostname_comboBox.Text;

                Thread toRunService = new Thread(new ThreadStart(validate));
                toRunService.Start();

                ((RallyDesk)parent).toolStripStatusLabel.Text = "Logging in..";
                ((RallyDesk)parent).ProgressBarMain.Style = ProgressBarStyle.Marquee;
                ((RallyDesk)parent).ProgressBarMain.Visible = true;

                while (toRunService.IsAlive)
                {
                   
                    Application.DoEvents();
                }

                toRunService.Abort();
                ((RallyDesk)parent).ProgressBarMain.Visible = false;
                ((RallyDesk)parent).toolStripStatusLabel.Text = "Ready";

                if (wk.Count == 0)
                {
                    // cmbUserName.Text = null;
                    txtPassword.Text = null;
                    //this.hostname_comboBox.Text = null;
                    RallyDesk.Username = null;
                    RallyDesk.Password = null;
                    RallyDesk.HOSTNAME = null;
                    MessageBox.Show(m_ResourceManager.GetString("memo://rallydesk/InvalidCredentials"), m_ResourceManager.GetString("memo://rallydesk/RallyDeskCaption"), MessageBoxButtons.OK, MessageBoxIcon.Warning);

                }
                else
                {
                    int i = 0;

                    for (i = 0; i < wk.Count; i++)
                    {
                        RallyDesk.WORKSPACENAMES.Add(((string[])(wk[i]))[0]);
                        RallyDesk.WORKSPACEREFERENCES.Add(((string[])(wk[i]))[1]);

                    }
                    RallyDesk.url = "https://" + RallyDesk.HOSTNAME + ".rallydev.com:443/slm/webservice/1.07/RallyService";

                    if (chkRememberMe.Checked)
                        SaveEnteriesInRegistry();
                    this.Close();


                }
            }
            catch (Exception)
            {

                throw;
            }
            finally
            {
                this.Enabled = true;
                this.Cursor = Cursors.Default;
            }
            
            
        }

        private void validate()
        {
            wk = service.ValidateCredentials(args);
            
        }

        private void LoginForm_Load(object sender, EventArgs e)
        {

            SetLoginData();
            LoadLoginDetails();
                     

        }

        private void button2_Click(object sender, EventArgs e)
        {
           this.Close();
        }

        private void LoginForm_KeyPress(object sender, KeyPressEventArgs e)
        {
            if (e.KeyChar == 13)
            {
                this.button1.PerformClick();
            }
        }
       

        private void txtPassword_KeyPress(object sender, KeyPressEventArgs e)
        {
            if (e.KeyChar == 13)
            {
                this.button1.PerformClick();
            }
        }
        
        private void LoadLoginDetails()
        {
            string statusOfRememberMe = Utilities.ReadRegistryKeyValue(LOGININFO, REMEMBERME);

            Utilities.ClearAll(this);
            string decryptedLoginText = string.Empty;            
            string decryptedPasswordText = string.Empty;
            string decryptedHostNameText = string.Empty;


            if (string.Compare(statusOfRememberMe, System.Boolean.TrueString) == 0)
            {
                decryptedLoginText = Utilities.Decrypt(Utilities.ReadRegistryKeyValue(LOGININFO, LOGINNAME), hashkey);                
                decryptedPasswordText = Utilities.Decrypt(Utilities.ReadRegistryKeyValue(LOGININFO, PASSWORD), hashkey);
                decryptedHostNameText = Utilities.Decrypt(Utilities.ReadRegistryKeyValue(LOGININFO, HOSTNAME), hashkey);


                cmbUserName.Text = decryptedLoginText;                
                txtPassword.Text = decryptedPasswordText;
                hostname_comboBox.Text = decryptedHostNameText;
            }
            //else populate it with the default values
            else
            {
                cmbUserName.Items.Clear();
                //hostname_comboBox.Items.Clear();                
            }

            chkRememberMe.Checked = string.Compare(statusOfRememberMe, System.Boolean.TrueString) == 0;
            
        }


        private void SaveEnteriesInRegistry()
        {
            bool chkChecked = chkRememberMe.Checked;

            string encryptedLoginText = chkChecked ? Utilities.Encrypt(cmbUserName.Text, hashkey) : string.Empty;
            string encryptedPasswordText = chkChecked ? Utilities.Encrypt(txtPassword.Text, hashkey) : string.Empty;
            string encryptedHostName = chkChecked ? Utilities.Encrypt(hostname_comboBox.Text, hashkey) : string.Empty;

            Utilities.WriteRegistryKeyValue(LOGININFO, LOGINNAME, encryptedLoginText);
            Utilities.WriteRegistryKeyValue(LOGININFO, PASSWORD, encryptedPasswordText);
            Utilities.WriteRegistryKeyValue(LOGININFO, REMEMBERME, Convert.ToString(chkChecked));
            Utilities.WriteRegistryKeyValue(LOGININFO, HOSTNAME, encryptedHostName);

            //save the recently used list in registry.
            this.SaveLoginDetails(cmbUserName.Text, txtPassword.Text,hostname_comboBox.Text);

        }

        private void SaveLoginDetails(string loginName, string password, string hostName)
        {
            Hashtable folderDetails = Utilities.ReadRegistryKeyValues(RECENT_INFO);

            SortedList folderkey = new SortedList(folderDetails.Count);

            foreach (string keyName in folderDetails.Keys)
            {
                folderkey.Add(keyName, (string)folderDetails[keyName]);
            }

            Queue loginQueue = new Queue();
            Queue passwordQueue = new Queue();
            Queue hostNameQueue = new Queue();

            foreach (string key in folderkey.Keys)
            {
                if (key.StartsWith(LOGINNAME))
                {
                    loginQueue.Enqueue((string)folderkey[key]);
                }
                else if (key.StartsWith(PASSWORD))
                {
                    passwordQueue.Enqueue((string)folderkey[key]);
                }
                else if (key.StartsWith(HOSTNAME))
                {
                    hostNameQueue.Enqueue((string)folderkey[key]);
                }
            }

            if (loginQueue.Count == 5)
                loginQueue.Dequeue();

            if (passwordQueue.Count == 5)
                passwordQueue.Dequeue();

            if (hostNameQueue.Count == 5)
                hostNameQueue.Dequeue();

            string encryptedLoginText = Utilities.Encrypt(loginName, hashkey);
            string encryptedPasswordText = Utilities.Encrypt(password, hashkey);
            string encryptedHostNameText = Utilities.Encrypt(hostName, hashkey);

            loginQueue.Enqueue(encryptedLoginText);
            passwordQueue.Enqueue(encryptedPasswordText);
            hostNameQueue.Enqueue(encryptedHostNameText);

            IEnumerator enumerator = loginQueue.GetEnumerator();
            folderDetails.Clear();

            int counter = 1;
            while (enumerator.MoveNext())
            {
                if (!(folderDetails.ContainsValue((string)enumerator.Current)))
                    folderDetails.Add(LOGINNAME + Convert.ToString(counter++), (string)enumerator.Current);
            }

            enumerator = passwordQueue.GetEnumerator();
            counter = 1;
            while (enumerator.MoveNext())
            {
                if (!(folderDetails.ContainsValue((string)enumerator.Current)))
                    folderDetails.Add(PASSWORD + Convert.ToString(counter++), (string)enumerator.Current);
            }

            enumerator = hostNameQueue.GetEnumerator();
            counter = 1;
            while (enumerator.MoveNext())
            {
                if (!(folderDetails.ContainsValue((string)enumerator.Current)))
                    folderDetails.Add(HOSTNAME + Convert.ToString(counter++), (string)enumerator.Current);
            }

            Utilities.WriteRegistryKeyValues(RECENT_INFO, folderDetails, true);
        }

        private void SetLoginData()
        {
            Hashtable folderDetails = Utilities.ReadRegistryKeyValues(RECENT_INFO);
            Hashtable folderCurrent = new Hashtable();
            foreach (string key in folderDetails.Keys)
            {
                string strValue = (string)folderDetails[key];
                strValue = Utilities.Decrypt(strValue, hashkey);

                
                if (key.StartsWith(LOGINNAME))
                {
                    if (cmbUserName.Items.IndexOf(strValue) == -1)
                    {
                        cmbUserName.Items.Add(strValue);
                    }
                }

                if (key.StartsWith(HOSTNAME))
                {
                    if (hostname_comboBox.Items.IndexOf(strValue) == -1)
                    {
                        hostname_comboBox.Items.Add(strValue);
                    }
                }
                           
            }
        }

        private string SetPassword()
        {
            string returnString = string.Empty;
            try
            {
                Hashtable folderDetails = Utilities.ReadRegistryKeyValues(RECENT_INFO);
                string text = string.Empty;
                int index = 0;

                foreach (string data in folderDetails.Keys)
                {
                    if (data.StartsWith("Login"))
                    {
                        text = Utilities.Decrypt((string)folderDetails[data], hashkey);

                        if (text == cmbUserName.Text)
                        {
                            char ch = data[data.Length - 1];
                            index = ch - '0';
                            break;
                        }
                    }
                }

                returnString = Utilities.Decrypt((string)folderDetails["Password" + index], hashkey);
            }
            catch (Exception)
            {
                returnString = string.Empty;
            }


            return returnString;
        }

        private void cmbUserName_SelectedIndexChanged(object sender, EventArgs e)
        {
            txtPassword.Text = string.Empty;
            txtPassword.Text = SetPassword();
        }

        public void SetStatusOfForm(bool isLogin)
        {

          //  this.workspace_comboBox.Enabled = !isLogin;

            //if (isLogin == true)
            //    this.workspace_comboBox.Items.Clear();

            //this.continue_button.Enabled = !isLogin;
            this.hostname_comboBox.Enabled = isLogin;
            this.txtPassword.Enabled = isLogin;
            this.cmbUserName.Enabled = isLogin;
            this.button1.Enabled = isLogin;
            this.button2.Enabled = isLogin;
        }

        
    
    
    }
}